package com.sky.service.admin.impl;

import com.github.pagehelper.Constant;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.sky.constant.MessageConstant;
import com.sky.constant.StatusConstant;
import com.sky.dto.SetmealDTO;
import com.sky.dto.SetmealPageQueryDTO;
import com.sky.exception.BaseException;
import com.sky.mapper.category.DishMapper;
import com.sky.mapper.category.SetmealDishMapper;
import com.sky.mapper.category.SetmealMapper;
import com.sky.pojo.Dish;
import com.sky.pojo.Setmeal;
import com.sky.pojo.SetmealDish;
import com.sky.result.PageResult;
import com.sky.service.admin.SetmealService;
import com.sky.vo.SetmealVO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.List;
import java.util.Optional;

@Service
@Slf4j
public class SetmealServiceImpl implements SetmealService {

    @Autowired
    private SetmealMapper setmealMapper;

    @Autowired
    private SetmealDishMapper setmealDishMapper;

    @Autowired
    private DishMapper dishMapper;


    /**
     * 分页查询套餐
     */
    @Override
    public PageResult pageQuery(SetmealPageQueryDTO dto) {
        PageHelper.startPage(dto.getPage(), dto.getPageSize());
        Page<Setmeal> page = setmealMapper.pageQuery(dto);
        return new PageResult(page.getTotal(), page);
    }

    /**
     * 新增套餐
     *
     * @param dto
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void save(SetmealDTO dto) {
        // 拷贝对象
        Setmeal setmeal = new Setmeal();
        BeanUtils.copyProperties(dto, setmeal);
        // 判断id是否为空
        Long id = dto.getId();
        Optional<Long> optional = Optional.ofNullable(id);
        if (optional.isEmpty()) {
            // id为空新增套餐
            // 设置套餐状态
            setmeal.setStatus(StatusConstant.DISABLE);
            // 调用mapper
            setmealMapper.add(setmeal);
            addSetmealDish(dto, setmeal);
        }
        // id不为空修改套餐
        Integer status = setmeal.getStatus();
        if (StatusConstant.ENABLE.equals(status)){
            //启售套餐,查询套餐中是否有禁用菜品
            List<SetmealDish> setmealDishes = setmealDishMapper.queryDishBySetmealId(setmeal.getId());
            List<Long> dishIds = setmealDishes.stream().map(setmealDish -> setmealDish.getDishId()).toList();
            List<Dish> dishes = dishMapper.queryNotOnsaleDishByIds(dishIds);
            if (!CollectionUtils.isEmpty(dishes)){
                //有停售状态菜品
                throw new BaseException(MessageConstant.SETMEAL_ENABLE_FAILED);
            }
        }
        setmealMapper.update(setmeal);
        //清空套餐菜品
        setmealDishMapper.delBySetmealIds(List.of(dto.getId()));
        addSetmealDish(dto,setmeal);

    }

    /**
     * 添加套餐菜品表
     * @param dto
     * @param setmeal
     */
    private void addSetmealDish(SetmealDTO dto, Setmeal setmeal) {
        List<SetmealDish> setmealDishes = dto.getSetmealDishes();
        if (CollectionUtils.isEmpty(setmealDishes)){
            return;
        }
        for (SetmealDish setmealDish : setmealDishes) {
            setmealDish.setSetmealId(setmeal.getId());
        }
        setmealDishMapper.add(setmealDishes);
    }

    /**
     * 根据id批量删除
     *
     * @param ids
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void delByIds(List<Long> ids) {
        //根据id查询是否有在售套餐
        List<Setmeal> setmeals = setmealMapper.queryOnsaleDishByIds(ids);
        if (!CollectionUtils.isEmpty(setmeals)){
            //有在售状态菜品
            throw new BaseException("删除套餐中存在在售状态套餐,请停售重新删除");
        }
        setmealMapper.delByIds(ids);
        // 删除套餐菜品表
        setmealDishMapper.delBySetmealIds(ids);
    }

    /**
     * 查询回显
     *
     * @param setmealId
     * @return
     */
    @Override
    public SetmealVO queryById(Long setmealId) {
        Setmeal setmeal = setmealMapper.queryById(setmealId);
        // 查询需要的菜品
        List<SetmealDish> setmealDishes = setmealDishMapper.queryDishBySetmealId(setmealId);
        SetmealVO vo = new SetmealVO();
        // 封装整合数据
        BeanUtils.copyProperties(setmeal, vo);
        vo.setSetmealDishes(setmealDishes);
        // 将数据整合封装
        return vo;
    }

}
